package view

import (
	"cloudops/src/common"
	"cloudops/src/config"
	"cloudops/src/models"
	"fmt"
	"github.com/gin-gonic/gin"
	"github.com/go-playground/validator/v10"
	"go.uber.org/zap"
	"strconv"
)

// 获取工单模板列表
func getWorkOrderTemplateList(c *gin.Context) {
	sc := c.MustGet(common.GIN_CTX_CONFIG_CONFIG).(*config.ServerConfig)
	currentPage, _ := strconv.Atoi(c.DefaultQuery("page", "1"))
	pageSize, _ := strconv.Atoi(c.DefaultQuery("pageSize", "100"))

	//多种资源共用的query
	searchUserID := c.DefaultQuery("UserID", "")
	searchUserIDInt, _ := strconv.Atoi(searchUserID)
	searchName := c.DefaultQuery("Name", "")

	// 代表是否有查询条件，用作这个total的计算
	hasSearch := false
	if searchUserID+searchName != "" {
		hasSearch = true
	}

	offset := 0
	limit := 0
	limit = pageSize
	if currentPage > 1 {
		offset = (currentPage - 1) * limit
	}

	// 数据库中拿到的所有的工单模板
	objs, err := models.GetWorkOrderTemplateAll()
	if err != nil {
		sc.Logger.Error("获取工单模板列表失败", zap.Error(err))
		common.ReqBadFailWithMessage(fmt.Sprintf("获取工单模板列表失败:%v", err.Error()), c)
		return
	}

	allIds := []int{}

	for _, obj := range objs {
		obj := obj
		if searchName != "" && obj.Name == searchName {
			continue
		}

		if searchUserID != "" && int(obj.UserID) == searchUserIDInt {
			continue
		}
		allIds = append(allIds, int(obj.ID))
	}

	if len(allIds) == 0 {
		common.OkWithDetailed(allIds, "ok", c)
		return
	}

	objs, err = models.GetWorkOrderTemplateByIdsWithLimitOffset(allIds, limit, offset)
	if err != nil {
		sc.Logger.Error("获取工单模板列表失败", zap.Error(err))
		common.ReqBadFailWithMessage(fmt.Sprintf("获取工单模板列表失败:%v", err.Error()), c)
		return
	}

	// 填充前端需要的数据，比如关联的formdesign和process的名字
	for _, obj := range objs {
		obj := obj
		obj.FillFrontAllDataOrOrderTemplate()
	}

	var total int
	if hasSearch {
		total = models.GetProcessCount()
	} else {
		total = len(allIds)
	}
	resp := &ResponseResourceCommon{
		Total: total,
		Items: objs,
	}
	common.OkWithDetailed(resp, "ok", c)
}

// 创建工单模版
func createWorkOrderTemplate(c *gin.Context) {
	sc := c.MustGet(common.GIN_CTX_CONFIG_CONFIG).(*config.ServerConfig)
	var reqObj models.WorkOrderTemplate
	err := c.ShouldBindJSON(&reqObj)
	if err != nil {
		sc.Logger.Error("创建工单模版失败", zap.Any("工单模版", reqObj), zap.Error(err))
		common.ReqBadFailWithMessage(err.Error(), c)
		return
	}

	err = validate.Struct(reqObj)
	if err != nil {
		if errors, ok := err.(validator.ValidationErrors); ok {
			common.ReqBadFailWithWithDetailed(
				gin.H{
					"翻译前": err.Error(),
					"翻译后": errors.Translate(trans),
				},
				"请求出错",
				c,
			)
			return
		}
		common.ReqBadFailWithMessage(err.Error(), c)
	}
	userName := c.MustGet(common.GIN_CTX_JWT_USER_NAME).(string)
	dbUser, err := models.GetUserByName(userName)
	if err != nil {
		sc.Logger.Error("获取用户失败", zap.Error(err))
		common.ReqBadFailWithMessage(fmt.Sprintf("用户不存在：%v", err.Error()), c)
		return
	}

	reqObj.UserID = dbUser.ID
	err = reqObj.CreateOneWorkOrderTemplate()
	if err != nil {
		sc.Logger.Error("创建工单模版失败", zap.Any("工单模版", reqObj), zap.Error(err))
		common.FailWithMessage(err.Error(), c)
		return
	}

	common.OkWithMessage("创建成功", c)
}

// 删除工单模版
func deleteWorkOrderTemplate(c *gin.Context) {
	sc := c.MustGet(common.GIN_CTX_CONFIG_CONFIG).(*config.ServerConfig)
	id, err := strconv.Atoi(c.Param("id"))
	sc.Logger.Info("删除工单模版", zap.Any("id", id))

	// 在数据库获取工单的ID
	intVar, err := strconv.Atoi(c.Param("id"))
	dbReq, err := models.GetWorkOrderTemplateById(intVar)
	if err != nil {
		sc.Logger.Error("删除工单模版失败", zap.Any("工单模板", id), zap.Error(err))
		common.FailWithMessage(err.Error(), c)
		return
	}
	err = dbReq.DeleteOneWorkOrderTemplate()
	if err != nil {
		sc.Logger.Error("删除工单模版失败", zap.Any("工单模板", id), zap.Error(err))
		common.ReqBadFailWithMessage(err.Error(), c)
		return
	}
	common.OkWithMessage("删除成功", c)
}

// 更新工单模版
func updateWorkOrderTemplate(c *gin.Context) {
	sc := c.MustGet(common.GIN_CTX_CONFIG_CONFIG).(*config.ServerConfig)
	var reqObj models.WorkOrderTemplate
	err := c.ShouldBindJSON(&reqObj)
	if err != nil {
		sc.Logger.Error("更新工单模版失败", zap.Any("工单模版", reqObj), zap.Error(err))
		common.ReqBadFailWithMessage(err.Error(), c)
		return
	}
	// 字段校验
	err = validate.Struct(reqObj)
	if err != nil {
		if errors, ok := err.(validator.ValidationErrors); ok {
			common.ReqBadFailWithWithDetailed(
				gin.H{
					"翻译前": err.Error(),
					"翻译后": errors.Translate(trans),
				},
				"请求出错",
				c,
			)
			return
		}
		common.ReqBadFailWithMessage(err.Error(), c)
		return
	}
	_, err = models.GetWorkOrderTemplateById(int(reqObj.ID))
	if err != nil {
		sc.Logger.Error("更新工单模版失败", zap.Any("工单模版", reqObj), zap.Error(err))
		common.FailWithMessage(err.Error(), c)
		return
	}
	err = reqObj.UpdateOneWorkOrderTemplate()
	if err != nil {
		sc.Logger.Error("更新工单模版失败", zap.Any("工单模版", reqObj), zap.Error(err))
		common.FailWithMessage(err.Error(), c)
		return
	}
	common.OkWithMessage("更新成功", c)
}

// 获取工单模版详情
func getWorkOrderTemplateDetail(c *gin.Context) {
	sc := c.MustGet(common.GIN_CTX_CONFIG_CONFIG).(*config.ServerConfig)
	id := c.Param("id")
	sc.Logger.Info("获取工单模版详情", zap.Any("id", id))
	intVar, err := strconv.Atoi(id)
	dbObj, err := models.GetWorkOrderTemplateById(intVar)
	if err != nil {
		sc.Logger.Error("获取工单模版详情失败", zap.Any("工单模版", id), zap.Error(err))
		common.OkWithMessage(err.Error(), c)
		return
	}
	dbObj.FillFrontAllDataOrOrderTemplate()
	common.OkWithDetailed(dbObj, "获取工单详情成功", c)
}
